package com.mymarkdown.app.util;

import java.io.File;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Objects;
import java.util.UUID;
import java.util.concurrent.BlockingQueue;

import cn.hutool.core.io.watch.WatchMonitor;
import cn.hutool.core.io.watch.Watcher;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.filefilter.FileFilterUtils;
import org.apache.commons.io.filefilter.HiddenFileFilter;
import org.apache.commons.io.filefilter.IOFileFilter;
import org.apache.commons.io.monitor.FileAlterationListenerAdaptor;
import org.apache.commons.io.monitor.FileAlterationMonitor;
import org.apache.commons.io.monitor.FileAlterationObserver;
import org.jsoup.nodes.Document;
import org.jsoup.select.Elements;

import com.mymarkdown.app.common.constant.Constant;

import cn.hutool.core.util.StrUtil;

/**
 * @author zenglun
 * @date 2021/12/7 11:39 上午
 * @description: TODO
 */
@Slf4j
public class FileUtil {
    private static SimpleDateFormat simpleDateFormat = new SimpleDateFormat("YYYY-MM-DD");

    private static String BASE_CREATE_UNDEFINED_NAME = "undefined";

    private FileUtil() {
    }

    /**
     * 获取随机文件名，采用UUID
     *
     * @return
     */
    public static String getRandomFileName() {
        return UUID.randomUUID().toString().replaceAll("-", "");
    }

    /**
     * 获取当前日期文件名
     *
     * @return
     */
    public static String getDateFileName() {
        return simpleDateFormat.format(Calendar.getInstance().getTime()) + "_" + System.currentTimeMillis();
    }


    /**
     * 根据当前文件夹获取一个未定义的文件夹
     */
    public static File getCurrentDirFileName(File file, String suffix) {
        if (!file.exists()) {
            log.warn("[FileUtil]---[getCurrentDirFileName],当前文件夹不存在, filepath:{}!", file.getPath());
            return null;
        }
        if (!file.isDirectory()) {
            log.warn("[FileUtil]---[getCurrentDirFileName],传入文件对象不是文件夹, filepath:{}!", file.getPath());
            return null;
        }
        String filename = file.getPath() + "/" + BASE_CREATE_UNDEFINED_NAME + suffix;

        File newCreateFile = null;
        for (int i = 1; (newCreateFile == null || newCreateFile.exists()); i++) {
            newCreateFile = new File(filename);
            filename = file.getPath() + "/" + BASE_CREATE_UNDEFINED_NAME + "_" + i + suffix;
        }

        return newCreateFile;
    }

    /**
     * 将客户端图片中的本地连接替换为当前服务器的远程地址连接
     *
     * @param parse HTML文档对象
     */
    public static void replaceLocalFileToRemote(Document parse) {
        // 首先获取所有的Image
        Elements imgElements = parse.select("img");

        imgElements.forEach(el -> {
            String attr = el.attr("src");
            if (StrUtil.isNotBlank(attr)) {
                // 如果不等于null
                attr = localLinkToRemeote(attr);
                el.attr("src", attr);
            }
        });

    }

    private static String localLinkToRemeote(String src) {

        if (StrUtil.isBlank(src)) {
            return src;
        }

        // 去除当前访问路径
        if (StrUtil.startWith(src, "/view")) {
            src = src.replace("/view", "");
        }

        if (StrUtil.startWith(src, "http://") || StrUtil.startWith(src, "https://")) {
            // 如果是远程地址
            return src;
        }
        // 如果是上一级
        BlockingQueue<File> operationFile = CurrentUserUtil.getSelf().getOperationFile();
        File peek = operationFile.peek();
        // 如果不是
        if (StrUtil.startWith(src, "../")) {

            if (Objects.isNull(peek)) {
                throw new NullPointerException("未找到相关文件!");
            }
            return String.format(Constant.BASE_IMAGE_PATH, getFileAddr(src, peek));
        }
        // 如果是上一级目录
        if (StrUtil.startWith(src, "/")) {
            return src;
        }
        return String.format(Constant.BASE_IMAGE_PATH, peek.getParent() + "/" + src);
    }

    private static String getFileAddr(String src, File file) {
        if (StrUtil.startWith(src, "../")) {
            return getFileAddr(src.replace(src, "../"), file.getParentFile());
        }
        return file.getParent() + "/" + src;
    }

}
